package py.una.pol.pweb.compraventa.jsfs;

import py.una.pol.pweb.compraventa.modelos.Venta;
import py.una.pol.pweb.compraventa.jsfs.util.JsfUtil;
import py.una.pol.pweb.compraventa.jsfs.util.PaginationHelper;
import py.una.pol.pweb.compraventa.ejbs.VentaFacade;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Iterator;
import java.util.List;
import java.util.ResourceBundle;
import javax.ejb.EJB;
import javax.faces.application.FacesMessage;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.SessionScoped;
import javax.faces.component.UIComponent;
import javax.faces.context.FacesContext;
import javax.faces.convert.Converter;
import javax.faces.convert.FacesConverter;
import javax.faces.model.DataModel;
import javax.faces.model.ListDataModel;
import javax.faces.model.SelectItem;
import py.una.pol.pweb.compraventa.modelos.Cliente;
import py.una.pol.pweb.compraventa.modelos.Producto;
import py.una.pol.pweb.compraventa.modelos.Ventadetalle;

@ManagedBean(name = "ventaController")
@SessionScoped
public class VentaController implements Serializable {

    private Venta current;
    private DataModel items = null;
    @EJB
    private py.una.pol.pweb.compraventa.ejbs.VentaFacade ejbFacade;
    @EJB
    private py.una.pol.pweb.compraventa.ejbs.ProductoFacade productofacade;
    @EJB
    private py.una.pol.pweb.compraventa.ejbs.VentadetalleFacade ventadetallefacade;
    @EJB
    private py.una.pol.pweb.compraventa.ejbs.ClienteFacade clientefacade;
    
    private PaginationHelper pagination;
    private int selectedItemIndex;
    private Cliente clienteSelected=new Cliente();
    private Producto productoSelected=new Producto();
    private double cantidadAVender=0;
    List<Producto> listaAVender = new ArrayList<Producto>();
    public List <Ventadetalle> ventaDetalleRealizado;

    public List<Ventadetalle> getVentaDetalleRealizado() {
        return ventaDetalleRealizado;
    }

    public void setVentaDetalleRealizado(List<Ventadetalle> ventaDetalleRealizado) {
        this.ventaDetalleRealizado = ventaDetalleRealizado;
    }
    Producto productoAVenderSelected=new Producto();
    public Producto productoAVender;

    public Producto getProductoAVender() {
        return productoAVender;
    }

    public void setProductoAVender(Producto productoAVender) {
        this.productoAVender = productoAVender;
    }
    
    
    public void confirmarProductoAVender() {


        FacesContext context = FacesContext.getCurrentInstance();
        try {
            //código para actualizar el saldo del cliente y el stock del producto
            ventaDetalleRealizado = new ArrayList<Ventadetalle>();

            if (clienteSelected.getIdcliente() == null) {
                throw new Exception();
            }

            current = new Venta();
            current.setIdcliente(clienteSelected);
            current.setNrofactura("");
            Calendar c1 = Calendar.getInstance();
            current.setFecha(c1.getTime());


            Cliente userx =  clientefacade.find(clienteSelected.getIdcliente());

            for (Producto elemento : listaAVender) {

                userx.setSaldo(userx.getSaldo()+(elemento.getCantidad()*elemento.getPrecioventa()));
                Producto productox = productofacade.find(elemento.getIdproducto());
                productox.setCantidad(productox.getCantidad() - elemento.getCantidad());
                Ventadetalle ventadetallex = new Ventadetalle();
                ventadetallex.setIdproducto(productox);

                ventadetallex.setIdventa(current);
                ventadetallex.setCantidad(cantidadAVender);
                ventadetallex.setObservaciones("");
                ventadetallex.setPreciocompra(productox.getPreciocompra());

                ventadetallex.setPrecioventa(productox.getPrecioventa());
                //compradetallefacade.create(compradetallex);
                ventaDetalleRealizado.add(ventadetallex);
                productofacade.edit(productox);

            }
            current.setVentadetalleCollection(ventaDetalleRealizado);
            clientefacade.edit(userx);
            create();
            clienteSelected = new Cliente();
            listaAVender = new ArrayList<Producto>();
            context.addMessage(null, new FacesMessage("Se registró la venta correctamente", "agregado correctamete."));



        } catch (Exception e) {

            context.addMessage(null, new FacesMessage("Ocurrió un error al registrar la venta", "agregado correctamete."));

        } finally {
            //em.close();
        }


    }
    
     public void agregarProductoAVender() {

        productoAVender = new Producto();
        productoAVender.setIdproducto(productoSelected.getIdproducto());
        productoAVender.setNombre(productoSelected.getNombre());
        productoAVender.setDescripcion(productoSelected.getNombre());
        productoAVender.setPreciocompra(productoSelected.getPrecioventa());
        productoAVender.setPrecioventa(productoSelected.getPrecioventa());
        productoAVender.setCantidad((int)cantidadAVender);
        Iterator iter = listaAVender.iterator();
        boolean existe = false;
        //listaAVender.add(productoAVender);
        
        while (iter.hasNext()) {
            Producto productoActual = (Producto) iter.next();
            System.out.println(productoAVender.getNombre());
            if (productoActual.getIdproducto() == productoAVender.getIdproducto()) {
                
                existe = true;
                FacesContext context = FacesContext.getCurrentInstance();
                context.addMessage(null, new FacesMessage("Error", "Ya se cargo este producto, elimine de la lista para cambiar"));

            }
        }
        if (existe==false){
            listaAVender.add(productoAVender);
            FacesContext context = FacesContext.getCurrentInstance();
            context.addMessage(null, new FacesMessage("Exito", "Se agregó el producto al carrito"));

        }
    }
    
    public void eliminarProductoAVender(){
        
        List <Producto> aux=new ArrayList<Producto>();
        Iterator it=listaAVender.iterator();
        while (it.hasNext()) {

            Producto element = (Producto)it.next();
            if (productoAVenderSelected!=null){
                if (element.getIdproducto()!=productoAVenderSelected.getIdproducto()){
                    //listaAVender.remove(element);
                    //break;
                    aux.add(element);
                    FacesContext context = FacesContext.getCurrentInstance();
                    context.addMessage(null, new FacesMessage(productoAVenderSelected.getIdproducto().toString(), "Se agregó el producto al carrito"));                    
                }else{

                }
                
            }else{
                FacesContext context = FacesContext.getCurrentInstance();
                context.addMessage(null, new FacesMessage("no se selecciono registro", "Se agregó el producto al carrito"));
            }
            

        }
        listaAVender=aux;
        
        
    
    }  
    
    public Producto getProductoAVenderSelected() {
        return productoAVenderSelected;
    }

    public void setProductoAVenderSelected(Producto productoAVenderSelected) {
        this.productoAVenderSelected = productoAVenderSelected;
    }



    public List<Producto> getListaAVender() {
        return listaAVender;
    }

    public void setListaAVender(List<Producto> listaAVender) {
        this.listaAVender = listaAVender;
    }

    public double getCantidadAVender() {
        return cantidadAVender;
    }

    public void setCantidadAVender(double cantidadAVender) {
        this.cantidadAVender = cantidadAVender;
    }

    public Producto getProductoSelected() {
        return productoSelected;
    }

    public void setProductoSelected(Producto productoSelected) {
        this.productoSelected = productoSelected;
    }
            
    public Cliente getClienteSelected() {
        return clienteSelected;
    }

    public void setClienteSelected(Cliente clienteSelected) {
        this.clienteSelected = clienteSelected;
    }

    public VentaController() {
    }

    public Venta getSelected() {
        if (current == null) {
            current = new Venta();
            selectedItemIndex = -1;
        }
        return current;
    }

    private VentaFacade getFacade() {
        return ejbFacade;
    }

    public PaginationHelper getPagination() {
        if (pagination == null) {
            pagination = new PaginationHelper(10) {
                @Override
                public int getItemsCount() {
                    return getFacade().count();
                }

                @Override
                public DataModel createPageDataModel() {
                    return new ListDataModel(getFacade().findRange(new int[]{getPageFirstItem(), getPageFirstItem() + getPageSize()}));
                }
            };
        }
        return pagination;
    }

    public String prepareList() {
        recreateModel();
        return "List";
    }

    public String prepareView() {
        current = (Venta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        return "View";
    }

    public String prepareCreate() {
        current = new Venta();
        selectedItemIndex = -1;
        return "Create";
    }

    public String create() {
        try {
            getFacade().create(current);
            JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("VentaCreated"));
            return prepareCreate();
        } catch (Exception e) {
            JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
            return null;
        }
    }

    public String prepareEdit() {
        current = (Venta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        return "Edit";
    }

    public String update() {
        try {
            getFacade().edit(current);
            JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("VentaUpdated"));
            return "View";
        } catch (Exception e) {
            JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
            return null;
        }
    }

    public String destroy() {
        current = (Venta) getItems().getRowData();
        selectedItemIndex = pagination.getPageFirstItem() + getItems().getRowIndex();
        performDestroy();
        recreatePagination();
        recreateModel();
        return "List";
    }

    public String destroyAndView() {
        performDestroy();
        recreateModel();
        updateCurrentItem();
        if (selectedItemIndex >= 0) {
            return "View";
        } else {
            // all items were removed - go back to list
            recreateModel();
            return "List";
        }
    }

    private void performDestroy() {
        try {
            getFacade().remove(current);
            JsfUtil.addSuccessMessage(ResourceBundle.getBundle("/Bundle").getString("VentaDeleted"));
        } catch (Exception e) {
            JsfUtil.addErrorMessage(e, ResourceBundle.getBundle("/Bundle").getString("PersistenceErrorOccured"));
        }
    }

    private void updateCurrentItem() {
        int count = getFacade().count();
        if (selectedItemIndex >= count) {
            // selected index cannot be bigger than number of items:
            selectedItemIndex = count - 1;
            // go to previous page if last page disappeared:
            if (pagination.getPageFirstItem() >= count) {
                pagination.previousPage();
            }
        }
        if (selectedItemIndex >= 0) {
            current = getFacade().findRange(new int[]{selectedItemIndex, selectedItemIndex + 1}).get(0);
        }
    }

    public DataModel getItems() {
        if (items == null) {
            items = getPagination().createPageDataModel();
        }
        return items;
    }

    private void recreateModel() {
        items = null;
    }

    private void recreatePagination() {
        pagination = null;
    }

    public String next() {
        getPagination().nextPage();
        recreateModel();
        return "List";
    }

    public String previous() {
        getPagination().previousPage();
        recreateModel();
        return "List";
    }

    public SelectItem[] getItemsAvailableSelectMany() {
        return JsfUtil.getSelectItems(ejbFacade.findAll(), false);
    }

    public SelectItem[] getItemsAvailableSelectOne() {
        return JsfUtil.getSelectItems(ejbFacade.findAll(), true);
    }

    @FacesConverter(forClass = Venta.class)
    public static class VentaControllerConverter implements Converter {

        public Object getAsObject(FacesContext facesContext, UIComponent component, String value) {
            if (value == null || value.length() == 0) {
                return null;
            }
            VentaController controller = (VentaController) facesContext.getApplication().getELResolver().
                    getValue(facesContext.getELContext(), null, "ventaController");
            return controller.ejbFacade.find(getKey(value));
        }

        java.lang.Integer getKey(String value) {
            java.lang.Integer key;
            key = Integer.valueOf(value);
            return key;
        }

        String getStringKey(java.lang.Integer value) {
            StringBuffer sb = new StringBuffer();
            sb.append(value);
            return sb.toString();
        }

        public String getAsString(FacesContext facesContext, UIComponent component, Object object) {
            if (object == null) {
                return null;
            }
            if (object instanceof Venta) {
                Venta o = (Venta) object;
                return getStringKey(o.getIdventa());
            } else {
                throw new IllegalArgumentException("object " + object + " is of type " + object.getClass().getName() + "; expected type: " + Venta.class.getName());
            }
        }
    }
}
